import { check } from 'meteor/check';
import { JoinServer } from 'meteor-publish-join';
import { Channels } from '/imports/models/Channels';
import { ChannelMembers } from '/imports/models/ChannelMembers';
import { ChannelMessages } from '/imports/models/ChannelMessages';

/**
 * 获取用户创建的频道列表
 * @param {Object} query
 * @param {Number} limit
 */
Meteor.publish('get.created.channels', function (query, limit) {
  check(limit, Number);

  const selector = {
    'owner.id': Meteor.userId()
  };

  Counts.publish(this, 'get.created.channels.counts', Channels.find(selector));

  return Channels.find(selector, {
    limit: limit,
    sort: {
      createdAt: -1
    }
  });
});

/**
 * 获取用户加入的所有频道
 * @param {Object} query
 * @param {Number} limit
 */
Meteor.publish('get.joined.channels', function (query, limit) {
  check(limit, Number);

  const selector = {
    user_id: Meteor.userId()
  };

  const pipeline = [{
      $match: selector
    },
    {
      $sort: {
        createdAt: -1
      }
    },
    {
      $lookup: {
        from: 'channels',
        localField: 'channel_id',
        foreignField: '_id',
        as: 'channels'
      },
    },
    {
      $addFields: {
        channel: {
          $arrayElemAt: ["$channels", 0]
        }
      }
    },
    {
      $project: {
        'channel._id': 1,
        'channel.channelId': 1,
        'channel.name': 1,
        'channel.cover': 1
      }
    },
    {
      $limit: limit
    }
  ];

  JoinServer.publish({
    context: this,
    name: 'get.joined.channels.counts',
    interval: 0,
    doJoin() {
      return ChannelMembers.find(selector).count();
    }
  });

  ReactiveAggregate(this, ChannelMembers, pipeline, {
    clientCollection: 'clientJoinedChannels'
  });
});

/**
 * 进入频道获取频道信息
 * @param {Object} query
 */
Meteor.publish('get.channel', function (query) {
  check(query.channelId, String);

  let selector = {
    channelId: query.channelId
  };

  return Channels.find(selector);
});

/**
 * 获取频道的聊天信息
 * @param {Object} query
 * @param {Number} limit
 */
Meteor.publish('get.channelMessages', function (query, limit) {
  check(query.channelId, String);
  check(limit, Number);

  const selector = {
    channelId: query.channelId
  };

  const pipeline = [{
      $match: selector
    },
    {
      $sort: {
        createdAt: -1
      }
    },
    {
      $lookup: {
        from: 'users',
        localField: 'userId',
        foreignField: '_id',
        as: 'users'
      },
    },
    {
      $addFields: {
        user: {
          $arrayElemAt: ["$users", 0]
        }
      }
    },
    {
      $project: {
        users: 0,
        'user.services': 0
      }
    },
    {
      $limit: limit
    }
  ];

  JoinServer.publish({
    context: this,
    name: 'get.channelMessages.counts',
    interval: 0,
    doJoin() {
      return ChannelMessages.find(selector).count();
    }
  });

  ReactiveAggregate(this, ChannelMessages, pipeline, {
    clientCollection: 'clientChannelMessages'
  });
});